#ifndef __FSM_HEADER
#define __FSM_HEADER

#include <memory>
#include <vector>
#include <string>

class FSMState;
class Deployment;
class TemplateSet;

//A vector of shared pointers housing all the states in the machine
typedef std::vector<std::shared_ptr<FSMState>> StateBank;

//---------------------------------------
//A Simple Finite State Machine
class FSM {
	public:
		FSM();
		FSM(std::string _name);
		FSM(Deployment * _dep);
		~FSM();
		int update();

		void transitionTo(std::string _stateName, int param = -1);
		void transitionBack();
		void delayTransitionTo(std::string _stateName);
		void addState(FSMState * _newState, bool _makeCurrent);
		std::string getState();
		
		friend class FSMState;

	private:
		FSMState *currentState;
		std::string delayState;
		Deployment * deployment;

		std::vector<std::string> history;

		//Bank to house list of states
		StateBank stateBank;
		std::vector<std::shared_ptr<FSMState>>::iterator iter;

};

//-----------------------------------------
//An individual state (must belong to a FSM)
//This is an abstract class and must be sub-classed
class FSMState {
	public:
		FSMState(FSM * _fsm) : fsm(_fsm) {};
		virtual ~FSMState(){};
		virtual int update() = 0;
		virtual void doEnter(int param){};
		virtual void doExit(){};	

		std::string stateName;  //used to switch between states
		FSM *fsm;
	protected:
		Deployment ** getDeployment();
		TemplateSet ** getSet();
};

#endif
